/*
 * @Author      : ZhouQiJun
 * @Date        : 2025-08-06 09:15:54
 * @LastEditors : ZhouQiJun
 * @LastEditTime: 2025-08-07 02:17:31
 * @Description :
 */

const EMPTY_STRING = ''

const DIGITS = 2

/**
 * 规格格式化静态类。
 */
export default class SpecsFormat {
  /**
   * 格式化长度
   * @param value 长度
   * @param prefix 前缀
   */
  public static toLength(value: number, prefix: string = EMPTY_STRING): string {
    if (value >= 1000) {
      return `${prefix}${SpecsFormat.toLocale(value / 1000)} (km)`
    } else if (value > 0) {
      return `${prefix}${SpecsFormat.toLocale(value)} (m)`
    }
    return EMPTY_STRING
  }

  /**
   * 格式化面积
   * @param value 面积
   * @param prefix 前缀
   */
  public static toArea(value: number, prefix: string = EMPTY_STRING): string {
    if (value >= 1000000) {
      return `${prefix}${SpecsFormat.toLocale(value / 1000000)} (km<sup>2</sup>)`
    } else if (value > 0) {
      return `${prefix}${SpecsFormat.toLocale(value)} (m<sup>2</sup>)`
    }
    return EMPTY_STRING
  }

  /**
   * 将小数经纬度转为度分秒字符串。
   * // FIXME 更好的名字 toDMS
   * @param coordinate 小数经纬度（[lon,lat]）
   * @param decimalPlaces 秒的小数位数，默认2位
   */
  public static toDegreeMinuteSecond(coordinate: number[], decimalPlaces: number = DIGITS): string[] {
    /**
     * 辅助函数：分解十进制度为度、分、秒，并保留原始符号
     * @param deg 十进制度数值（带符号）
     * @returns [带符号的度, 分, 秒]
     */
    const convert = (deg: number): [number, number, number] => {
      const isNegative = deg < 0
      const degAbs = Math.abs(deg)
      const degrees = Math.floor(degAbs) * (isNegative ? -1 : 1) // 度保留符号
      const minutesFloat = (degAbs - Math.abs(degrees)) * 60
      const minutes = Math.floor(minutesFloat)
      const seconds = (minutesFloat - minutes) * 60
      return [degrees, minutes, seconds]
    }

    // 转换经度（直接保留符号）
    const [lonDeg, lonMin, lonSec] = convert(coordinate[0])
    const lonDms = `${lonDeg}°${lonMin}′${lonSec.toFixed(decimalPlaces)}″`

    // 转换纬度（直接保留符号）
    const [latDeg, latMin, latSec] = convert(coordinate[1])
    const latDms = `${latDeg}°${latMin}′${latSec.toFixed(decimalPlaces)}″`

    return [lonDms, latDms]
  }

  private static toLocale(value: number): string {
    return value.toLocaleString(undefined, { maximumFractionDigits: DIGITS })
  }
}
